package cn.topcodes.tcsf.wechat.service;

import cn.topcode.unicorn.utils.EmojiUtil;
import cn.topcode.unicorn.utils.StringUtil;
import cn.topcode.unicorn.wxsdk.WechatMpDataSource;
import cn.topcode.unicorn.wxsdk.base.UserInfo;
import cn.topcode.unicorn.wxsdk.base.WechatMpInfo;
import cn.topcodes.tcsf.admin.commons.domain.ValueRangeConstant;
import cn.topcodes.tcsf.admin.domain.entity.SystemProperty;
import cn.topcodes.tcsf.admin.service.SystemPropertyService;
import cn.topcodes.tcsf.wechat.domain.entity.WechatMp;
import cn.topcodes.tcsf.admin.commons.generic.GenericService;
import cn.topcodes.tcsf.wechat.domain.entity.WechatUser;
import cn.topcodes.tcsf.wechat.domain.entity.WechatUserBranch;
import cn.topcodes.tcsf.wechat.service.utils.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;
import tk.mybatis.mapper.entity.Example;

import java.util.Date;

/**
 * 微信公众号 服务
 * @author Unicorn
 * @date 2018-03-20 15:56:31
 */
public class WechatMpServiceImpl extends GenericService<WechatMp> implements WechatMpService, WechatMpDataSource {

    public static final String CURRENT_MP_ID = "CURRENT_MP_ID";

    public static final String CURRENT_WECHAT_MP_ID = "CURRENT_WECHAT_MP_ID";

    public static final String DEFAULT_MP_ID = "DEFAULT_MP_ID";

    @Autowired
    private SystemPropertyService systemPropertyService;

    @Autowired
    private WechatUserService wechatUserService;

    @Autowired
    private WechatUserBranchService wechatUserBranchService;

    @Override
    public String getDefaultMpId() {
        String defaultMpId = this.systemPropertyService.findSysProperty(DEFAULT_MP_ID, String.class, null);
        if(StringUtil.isBlank(defaultMpId)) {
            WechatMp wechatMp = this.findOne(this.buildExample());
            if(wechatMp == null) {
                throw new IllegalStateException("未设置默认公众号ID");
            }else {
                defaultMpId = wechatMp.getMpId();
            }
        }
        return defaultMpId;
    }

    /**
     * 是否存在微信用户信息
     *
     * @param mpId   公众号ID
     * @param openId 用户openId
     * @return 是否存在
     */
    @Override
    public boolean existWechatUser(String mpId, String openId) {
        WechatMp wechatMp = this.findWechatMpByMpId(mpId);
        WechatUser wechatUser = wechatUserService.findBy(wechatMp.getId(), openId);
        return wechatUser != null;
    }

    /**
     * 保存微信用户信息
     *
     * @param mpId     公众号ID
     * @param userInfo 微信用户信息
     */
    @Override
    @Transactional(readOnly = false, rollbackFor = Exception.class)
    public void saveWechatUser(String mpId, UserInfo userInfo) {
        if(!existWechatUser(mpId, userInfo.getOpenId())) {
            WechatMp wechatMp = this.findWechatMpByMpId(mpId);
            WechatUser wechatUser = new WechatUser();
            wechatUser.setOpenId(userInfo.getOpenId());
            wechatUser.setNickname(EmojiUtil.emojiChange(userInfo.getNickname()));
            wechatUser.setSubscribe(WechatUser.SUBSCRIBE_FALSE);
            wechatUser.setCity(userInfo.getCity());
            wechatUser.setCountry(userInfo.getCountry());
            wechatUser.setHeadImgUrl(userInfo.getHeadImgUrl());
            wechatUser.setSubscribeTime(new Date());
            wechatUser.setProvince(userInfo.getProvince());
            if(userInfo.getSex() == 1) {
                wechatUser.setGender(ValueRangeConstant.Gender.GENDER_MALE);
            }else if(userInfo.getSex() == 2) {
                wechatUser.setGender(ValueRangeConstant.Gender.GENDER_FEMALE);
            }else {
                wechatUser.setGender(ValueRangeConstant.Gender.GENDER_UNKNOWN);
            }
            wechatUser.setUnionId(userInfo.getUnionId());
            this.wechatUserService.save(wechatUser);

            WechatUserBranch branch = new WechatUserBranch();
            branch.setType(WechatUserBranch.TYPE_MP);
            branch.setOpenId(userInfo.getOpenId());
            branch.setSubscribe(WechatUser.SUBSCRIBE_FALSE);
            branch.setUserId(wechatUser.getId());
            branch.setWechatMpId(wechatMp.getId());
            branch.setSubscribeTime(new Date());
            wechatUserBranchService.save(branch);
        }
    }

    @Override
    @Transactional(readOnly = false, rollbackFor = Exception.class)
    public void setDefaultMpId(String mpId) {
        Assert.isTrue(this.exist(WechatMp.FIELD_MP_ID, mpId), "公众号ID不存在");
        this.systemPropertyService.setSysProp(DEFAULT_MP_ID, mpId);
    }

    @Override
    public String getMpId(Long wechatMpId) {
        WechatMp wechatMp = this.findOne(wechatMpId);
        if(wechatMp != null) {
            return wechatMp.getMpId();
        }
        return null;
    }

    @Override
    public WechatMp findWechatMpByMpId(String mpId) {
        Example example = this.buildExample();
        example.or().andEqualTo(WechatMp.FIELD_MP_ID, mpId);
        return this.findOne(example);
    }

    @Override
    public String getCurrentMpId() {
        String currentMpId = this.systemPropertyService.findSysProperty(CURRENT_MP_ID, String.class, null);
        if(StringUtil.isBlank(currentMpId)) {
            WechatMp wechatMp = this.findOne(this.buildExample());
            if(wechatMp != null) {
                currentMpId = wechatMp.getMpId();
            }
        }
        return currentMpId;
    }

    @Override
    public String getCurrentWechatMpId() {
        String currentWechatMpId = this.systemPropertyService.findSysProperty(CURRENT_WECHAT_MP_ID, String.class, null);
        if(StringUtil.isBlank(currentWechatMpId)) {
            WechatMp wechatMp = this.findOne(this.buildExample());
            if(wechatMp != null) {
                currentWechatMpId = wechatMp.getId().toString();
            }
        }
        return currentWechatMpId;
    }

    @Override
    @Transactional(readOnly = false, rollbackFor = Exception.class)
    public void setCurrentMp(Long wechatMpId) {
        String mpId = this.getMpId(wechatMpId);
        SystemProperty mpIdProp = systemPropertyService.findSysProp(CURRENT_MP_ID);
        if(mpIdProp == null) {
            mpIdProp = new SystemProperty();
            mpIdProp.setType("String");
            mpIdProp.setDescription("当前公众号");
            mpIdProp.setName(CURRENT_MP_ID);
            mpIdProp.setValue(mpId);
            this.systemPropertyService.create(mpIdProp);
        }else {
            this.systemPropertyService.modifySysProp(CURRENT_MP_ID, mpId);
        }

        SystemProperty wechatMpIdProp = systemPropertyService.findSysProp(CURRENT_WECHAT_MP_ID);
        if(wechatMpIdProp == null) {
            wechatMpIdProp = new SystemProperty();
            wechatMpIdProp.setType("String");
            wechatMpIdProp.setDescription("当前公众号ID");
            wechatMpIdProp.setName(CURRENT_WECHAT_MP_ID);
            wechatMpIdProp.setValue(wechatMpId.toString());
            this.systemPropertyService.create(wechatMpIdProp);
        }else {
            this.systemPropertyService.modifySysProp(CURRENT_WECHAT_MP_ID, wechatMpId.toString());
        }
    }

    /**
     * 通过公众号ID查找公众号信息
     *
     * @param mpId
     * @return
     */
    @Override
    public WechatMpInfo findByMpId(String mpId) {
        WechatMp wechatMp = this.findWechatMpByMpId(mpId);
        if(wechatMp == null) {
            return null;
        }
        WechatMpInfo wechatMpInfo = new WechatMpInfo();
        wechatMpInfo.setName(wechatMp.getName());
        wechatMpInfo.setMpId(wechatMp.getMpId());
        wechatMpInfo.setMpUrl(wechatMp.getMpUrl());
        wechatMpInfo.setAppId(wechatMp.getAppId());
        wechatMpInfo.setSecret(wechatMp.getSecret());
        wechatMpInfo.setToken(wechatMp.getToken());
        wechatMpInfo.setLastGetTokenTimemillis(wechatMp.getLastGetTokenTimemillis());
        wechatMpInfo.setTokenExpires(wechatMp.getTokenExpires());
        wechatMpInfo.setJsTicket(wechatMp.getJsTicket());
        wechatMpInfo.setJsTicketExpires(wechatMp.getJsTicketExpires());
        wechatMpInfo.setLastGetJsTicketTimemillis(wechatMp.getLastGetJsTicketTimemillis());
        wechatMpInfo.setOpenAppId(wechatMp.getOpenAppId());
        wechatMpInfo.setOpenSecret(wechatMp.getOpenSecret());
        return wechatMpInfo;
    }

    /**
     * 保存公众号信息
     *
     * @param wechatMpInfo
     */
    @Override
    @Transactional(readOnly = false, rollbackFor = Exception.class)
    public void saveWechatMpInfo(WechatMpInfo wechatMpInfo) {
        WechatMp wechatMp = this.findWechatMpByMpId(wechatMpInfo.getMpId());
        if(wechatMp == null) {
            wechatMp = new WechatMp();
        }
        wechatMp.setName(wechatMpInfo.getName());
        wechatMp.setMpId(wechatMpInfo.getMpId());
        wechatMp.setMpUrl(wechatMpInfo.getMpUrl());
        wechatMp.setAppId(wechatMpInfo.getAppId());
        wechatMp.setSecret(wechatMpInfo.getSecret());
        wechatMp.setToken(wechatMpInfo.getToken());
        wechatMp.setLastGetTokenTimemillis(wechatMpInfo.getLastGetTokenTimemillis());
        wechatMp.setTokenExpires(wechatMpInfo.getTokenExpires());
        wechatMp.setJsTicket(wechatMpInfo.getJsTicket());
        wechatMp.setJsTicketExpires(wechatMpInfo.getJsTicketExpires());
        wechatMp.setLastGetJsTicketTimemillis(wechatMpInfo.getLastGetJsTicketTimemillis());
        wechatMp.setOpenAppId(wechatMpInfo.getOpenAppId());
        wechatMp.setOpenSecret(wechatMpInfo.getOpenSecret());
        this.save(wechatMp);
    }
}
